#include "app_main.h"
#include "user_config.h"
#include "app_uv_control.h"
#include "app_valve_control.h"
#include "app_eeprom_manage.h"
#include "app_print.h"
#include "app_uv_pwm.h"
#include "app_button.h"


// ============ WiFi强制重置变量 ============
// 解决问题: WiFi模块使用缓存的旧Product Key，导致手机搜不到设备
// 方案: 握手后2秒发送0x04重置命令，强制模块清除缓存并重新初始化
static uint8_t wifi_reset_done = 0;      // 重置完成标志
static uint32_t reset_timer = 0;         // 重置延迟计时器
// =========================================
// =========================================
extern bool_t wifi_data_sync_flag;

/**
 * @brief WiFi连接超时监控 - 防止长时间无法连接到云端
 * @param  无
 * @return 无
 * @note   超过60秒未连接到云端自动重置WiFi
 */
void app_wifi_connection_monitor(void)
{
    static uint32_t last_cloud_connect_time = 0;
    static uint8_t monitor_init = 0;

    // 初始化时间戳
    if(!monitor_init)
    {
        last_cloud_connect_time = DateUp_Time;
        monitor_init = 1;
    }

    // 已连接云端，更新时间戳
    if(wifi_work_state == WIFI_CONN_CLOUD)
    {
        last_cloud_connect_time = DateUp_Time;
    }
    // 超过60秒未连接到云端，重置WiFi
    else if(DateUp_Time - last_cloud_connect_time > 60000)
    {
#ifdef TUYA_PROTOCOL_DEBUG
        APP_PRINT(APP_MODULE_WIFI, "WiFi not connected to cloud for 60s, reset WiFi\r\n");
#endif

        mcu_reset_wifi();
        last_cloud_connect_time = DateUp_Time;  // 重置计时
    }
}
/**
 * @brief 主应用程序 - 完全参照 data.txt 的标准交互流程实现
 * @param  无
 * @return 无
 * @note
 *   data.txt 中的正确交互流程:
 *   1. 心跳检测 (0x00)      ← WiFi模块发起，协议栈自动回复
 *   2. 查询产品信息 (0x01)  ← WiFi模块发起，协议栈自动回复
 *   3. 查询工作模式 (0x02)  ← WiFi模块发起，协议栈自动回复
 *   4. 设备状态信息 (0x03)  ← WiFi模块发起，协议栈自动回复
 *   5. 心跳维持 (0x00)      ← 协议栈定期处理
 *
 *   关键原则: 让协议栈自动处理所有握手和通信
 *   MCU代码的唯一职责: 初始化 + 循环处理
 */
 
//变量
int TDS_Value;
float TEMP_Value,EC_Value;
CJHR31_Data_t humidityData;  //湿度结构体

int PH = 700;
int CA = 100;

/**
 * @brief  按键事件处理函数
 * @param  None
 * @retval None
 * @note   处理三个按键: "忽略1"、"忽略2"、"更换成功"
 */
void handle_button_events(void)
{
    // 处理"忽略1"按键 (PB13)
    if (app_button_get_ignore1())
    {
        g_user_config.uv_ignore_flag1 = 1;
        app_eeprom_set_ignore_flag(1, 1);
        UART5_Printf("[Button] Ignore1 pressed and set\r\n");

        // 如果当前在锁定状态,解除锁定
        if (g_user_config.uv_state == UV_STATE_LOCKED_WORKTIME)
        {
            g_user_config.uv_state = UV_STATE_IGNORE2_CHECK;
            UART5_Printf("[UV] Unlocked from WORKTIME by Ignore1\r\n");
        }
    }

    // 处理"忽略2"按键 (PB14)
    if (app_button_get_ignore2())
    {
        g_user_config.uv_ignore_flag2 = 1;
        app_eeprom_set_ignore_flag(2, 1);
        UART5_Printf("[Button] Ignore2 pressed and set\r\n");

        // 如果当前在锁定状态,解除锁定
        if (g_user_config.uv_state == UV_STATE_LOCKED_RADIATION)
        {
            g_user_config.uv_state = UV_STATE_RUNNING;
            UART5_Printf("[UV] Unlocked from RADIATION by Ignore2\r\n");
        }
    }

    // 处理"更换成功"按键 (PC3)
    if (app_button_get_replace())
    {
        app_eeprom_reset_uv_data();  // 清除UV工作时间和所有标志位
        UART5_Printf("[Button] Replace pressed - UV data reset\r\n");

        // 重新初始化状态机
        g_user_config.uv_state = UV_STATE_INIT;
        UART5_Printf("[UV] State machine reset to INIT\r\n");
    }
}

void app_main(void)
{
    //ALL_Init
    Init();

    // ========== 新增: 初始化用户配置和应用层模块 ==========
    user_config_init();            // 初始化全局配置结构体
    app_print_init();              // 初始化App打印模块
    app_eeprom_load_data();        // 从EEPROM加载历史数据(包括UV工作时间和忽略标志位)

    // ========== 新增: 初始化PWM和按键驱动 ==========
    app_uv_pwm_init();             // 初始化UV灯PWM控制(TIM1_CH1, PB12)
    app_button_init();             // 初始化按键驱动(PB13/PB14/PC3)

    app_uv_control_init();         // 初始化UV灯状态机控制
    app_valve_control_init();      // 初始化电磁阀控制

    // ========== RTC网络时间同步标志 ==========
    static uint8_t rtc_sync_done = 0;  // RTC是否已同步

    while(1)
    {
        // 这是唯一需要做的事: 处理协议通信
        // 所有复杂的握手逻辑都由协议栈内部自动完成
        wifi_uart_service();

        // ========== WiFi连接超时监控 ==========
        // 防止长时间无法连接到云端的情况(60秒超时)
        app_wifi_connection_monitor();

        // ============ WiFi强制重置逻辑(手动配网重置) ============
        // 原理: 握手后2秒发送0x04重置命令，让WiFi模块清除缓存并重新初始化
        // 效果: 强制获取最新Product Key，解决手机搜不到设备的问题
        extern bool_t is_heart;
        if (!wifi_reset_done && is_heart) {
            if (reset_timer == 0) {
                reset_timer = 1;                // 第一次进入，开始计时
            } else if (reset_timer < 2000) {
                reset_timer++;                  // 继续计时
            } else if (reset_timer == 2000) {
                mcu_reset_wifi();               // 发送0x04重置指令
                wifi_reset_done = 1;            // 标记已重置，不再执行
            }
        }
        
        // ========== 新增: UV灭菌控制逻辑(每100ms执行一次) ==========
        static uint32_t last_control_time = 0;
        if (DateUp_Time - last_control_time >= 100)
        {
            last_control_time = DateUp_Time;

            // 1. 按键扫描(100ms周期)
            app_button_scan();

            // 2. 按键事件处理
            handle_button_events();

            // 3. UV灯状态机控制逻辑(包含电磁阀控制)
            app_uv_control_process();

            // 4. EEPROM定时保存(5分钟保存1次)
            app_eeprom_auto_save();
        }

       // ========== RTC网络时间同步 ==========
       // 当WiFi连接到云服务器后(state=4),自动同步网络时间到DS3231
       if(wifi_work_state == 4 && rtc_sync_done == 0)
       {
           // 延迟5秒等待时间戳校准完成
           static uint32_t sync_wait_timer = 0;
           if(sync_wait_timer == 0)
           {
               sync_wait_timer = DateUp_Time;
           }
           else if(DateUp_Time - sync_wait_timer >= 5000)  // 等待5秒
           {
               mcu_get_system_time();  // 发送获取时间请求(0x1c命令)
               rtc_sync_done = 1;      // 标记已请求,避免重复
               APP_PRINT(APP_MODULE_RTC, "Requesting network time sync...\r\n");
           }
       }

       //程序需要先将涂鸦wifi配置完毕之后才可以获取数据 才可以屏幕显示的
       if(wifi_work_state == 4)
       {
           //获取总流量、瞬时流量
            Flow_Read();
           
            /*获取TDS、EC、Temp使用定时器6定时操作 间隔1s*/ 
            if(RX[0] == 0xAA)
            {
                 TDS_Value = RX[1]*256 + RX[2];//溶解固体
                 TEMP_Value = (RX[3]*256 + RX[4])/100.0f;//温度
                 EC_Value = TDS_Value/0.6;//电导率

                 __nop();
                     
                /*湿度传感器*/
                if(CJHR31_ReadHumidity(&humidityData,(int)(TEMP_Value * 10)) == CJHR31_OK)
                {
//                    APP_PRINT(APP_MODULE_SENSOR, "湿度: %f %%RH\r\n", humidityData.humidity);
//                    APP_PRINT(APP_MODULE_SENSOR, "温度: %d °C\r\n", humidityData.temperature);
                }
            }        
            
             /*获取Uv辐射度使用定时器6定时操作*/
            if(Uv_Time > 500)
            {
                /*读取UV值并打印*/
                g_user_config.uv_radiation = LTR390_UVS();

                Uv_Time = 0;
            }
            
            /*串口打印*/
            if(Printf_Time >= 1000)
            {
                Printf_Time = 0;
                get_show_time();		//获取时间
                get_show_Temperature();		//获取温度
                //打印从DS3231MZ获取的时间
                UART5_Printf("%d年%d月%d日%d时%d分%d秒 星期%d 温度%d\"\xff\xff\xff",calendar.year+2000,calendar.month,calendar.date,\
                                calendar.hour,calendar.min,calendar.sec,calendar.week,calendar.temperature);
                UART5_Printf("\r\n");
                //打印当前UV辐射度
                UART5_Printf("UV = %d\r\n", (uint32_t)g_user_config.uv_radiation);
                //总水量、瞬时流量、
                UART5_Printf("瞬时流量:%f\r\n",golbal_flow.instant);
                UART5_Printf("总流量:%f\r\n",golbal_flow.acculat);
                //温度、TDS、EC、
                UART5_Printf("TDS:%d\r\n",TDS_Value);//总溶解固体
                UART5_Printf("Temp:%f\r\n",TEMP_Value);//温度
                UART5_Printf("EC:%f\r\n",EC_Value);//电导率   
            }

            /*屏幕刷新*/
            if(Screen_Time > 500)
            {
                Screen_Time = 0;
                //温度、TDS、EC
                tjc_send_val("x0", "val", (int)(TEMP_Value * 10));//温度
                tjc_send_val("x2", "val", (int)(EC_Value * 10));//EC
                tjc_send_val("x3", "val", (int)(TDS_Value * 10));//TDS
                //流量
                int flow_instant = (int)(golbal_flow.instant * 10); // 瞬时流量
                int flow_acculat = (int)(golbal_flow.acculat * 10); // 总流量
                tjc_send_val("x4", "val", flow_instant);//瞬时流量
                tjc_send_val("x1", "val", flow_acculat);//总流量
                //UV辐射
                tjc_send_val("x6", "val", (int)g_user_config.uv_radiation*10);//辐射度--->取消小数点
            }
            /*数据涂鸦上报*/
            if(DateUp_Time > 5000)
            {
                DateUp_Time = 0;
                mcu_dp_value_update(DPID_TDS_IN, TDS_Value * 10);
                mcu_dp_value_update(DPID_TEMP_CURRENT, TEMP_Value*10);
                mcu_dp_value_update(DPID_UV_VALUE, g_user_config.uv_radiation * 10);
                mcu_dp_value_update(DPID_PH, PH);
                mcu_dp_value_update(DPID_CA_VALUE, CA);
                
                CA = CA + 100;
                PH = PH + 100;     
                APP_PRINT(APP_MODULE_MAIN, "PH:%d\r\n",PH);
             }
            
       }
  
        
        LED_O;
        delay_ms(500);
        LED_F;
        delay_ms(500);
        
        
    }
}



/*
EEPROM:测试
    uint8_t RootData[4] = {2,0,2,5};//管理员密码
    uint8_t MimaData[4] = {0,1,2,1};//开锁密码
    
    uint8_t Mima[4]={0};//存放读取的开锁密码
    uint8_t Root[4]={0};//存放读取的开锁密码

    UART5_Printf("Mima内容:%d %d %d %d\n",Mima[0],Mima[1],Mima[2],Mima[3]);  
    UART5_Printf("Root内容:%d %d %d %d\n",Root[0],Root[1],Root[2],Root[3]); 
    // 写入数据
    EEPROM_WriteMulti(0x00, RootData, 4);//写入Root密码
    delay_ms(10);
    EEPROM_WriteMulti(0x10, MimaData, 4);//写入开锁密码
    delay_ms(10);
    
    
    EEPROM_ReadMulti(0x10, Mima, 4);//读取开锁密码
    EEPROM_ReadMulti(0x00, Root, 4);//读取ROtt密码
    UART5_Printf("Mima内容:%d %d %d %d\n",Mima[0],Mima[1],Mima[2],Mima[3]);  
    UART5_Printf("Root内容:%d %d %d %d\n",Root[0],Root[1],Root[2],Root[3]); 
W25Q64:测试
    uint8_t wifiname[10] = "xxg1";
    uint8_t name[10] = {0};
    UART5_Printf("1=========name=%s\r\n",name);
    sFLASH_EraseSector(0x009000);//先擦除 将数据写为1
    //存放WiFi名称内容 
    sFLASH_WriteBuffer(wifiname,0x009000+2,strlen((char *)wifiname));//将数据写入w25q64中
    //读取
    sFLASH_ReadBuffer(name,0x009000+2,4);
    UART5_Printf("2++++++name=%s\r\n",name);    
    
    
    
    
    
    
    
    
    
    
    
    
            
        if(Uv_Config_Time >= 200)
        {
            Uv_Config_Time = 0;
            
                if（瞬时流量 大于等于阈值 || Wrok_SpareTime >= SPARETIME）
                {
                    UvLight_Open;
                    Wrok_BusyTime = 0;
                    UvWrok_Busy_Flag = 1;
                    
                }else if(瞬时流量 小于阈值 || Wrok_BusyTime >= WORKTIME)
               {
                    UvLight_Close;
                    Wrok_SpareTime = 0;
                    UvWrok_Busy_Flag = 0;
                }
                
            
        }
       
       
        //检测当前Uv灯是否开启 如果开启 那么就是使能定时器 如果关闭失能定时器
        if(Uv_State_Time >= 800)
        {
            Uv_State_Time = 0;
            if(Read_Uv_State == 1)
            {
                //读取此时Work_Time--->第一次Work_Time如何保存到EEPROM中...
                TIM_Cmd(TIM7, ENABLE);
            }               
            else
            {
                TIM_Cmd(TIM7, DISABLE);
                //保存此时的Work_Time
            }               
        }
    
    
    

    
    
    
    
    
*/
